package com.hmjk.health;

import java.io.BufferedReader;
import java.io.File;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map.Entry;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import com.baidu.mapapi.SDKInitializer;
import com.hmjk.health.background.DataManager;
import com.hmjk.health.background.MqttService;
import com.hmjk.health.setting.SettingsConstants;
import com.hmjk.health.util.ADInfo;
import com.hmjk.health.util.ADose;
import com.hmjk.health.util.GlycoseData;
import com.hmjk.health.views.CustomDialog;
import com.umeng.update.UmengUpdateAgent;
import com.umeng.update.UmengUpdateListener;
import com.umeng.update.UpdateResponse;
import com.umeng.update.UpdateStatus;

import android.app.Activity;
import android.app.AlertDialog;
import android.app.Application;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.os.Handler;
import android.os.Message;
import android.os.Vibrator;
import android.util.Base64;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.animation.Animation;
import android.view.animation.AnimationUtils;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.Toast;
import android.widget.ImageView.ScaleType;
import android.widget.TextView;
import android.content.Context;
import android.content.DialogInterface;
import android.content.DialogInterface.OnCancelListener;
import android.content.DialogInterface.OnDismissListener;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.SharedPreferences.Editor;

public class HealthApp extends Application{
	private final static String TAG = "HealthApp";
	/*唯一的数据库实例，需共享的数据和对象都放在app里*/
	//private ArrayList<ADInfo> mADArray = new ArrayList<ADInfo>();
	public static final int AD_MAX_NUM = 3;
	private String mLastVisit = null;
	private boolean userSignIn = false;
	private String mUser = null;
	private String mPassword = null;
//	private String mRememberUID = null;
	
	private SharedPreferences mPref = null;
	private static File appPath = null;
//	private String savedIdentifyCode = null;
	private Activity mCurActivity = null;
	private String mUID = null;
	private String mSession = null;
	//private SessionTimeUp mSTimeUp = null;
	
	private boolean newVersion = false;
	
	private DataManager mDataManager = null;
	private String mEnterType;
	
	//MQTT Settings
	private boolean isMQTTMsgOn = false, isMQTTSoundOn = false, isMQTTVibOn = false;
	
	public final static String ACTION_SIGN_IN_OUT = "com.hmjk.action.sign_in_out";
	//public final static String ACTION_AD_UPDATE = "com.hmjk.action.ad_update";
	
	private HashMap<String, ADInfo> mADInfo = null;
	
	//ADose choose list
	private List<ADose> doseChooseList = new ArrayList<ADose>();
	private final String DRUG_LIST_FILE = "drug";
	
	private boolean AD_DEBUG = false;
	public final void ADDebug(String info){
		if(AD_DEBUG){
			Log.d("AD_DEBUG", info);
		}
	}
	
	private void logd(String info){
		Log.d(TAG, info);
	}
	
	public void setEnterType(String type){
		mEnterType = type;
	}
	
	public String getEnterType(){
		return mEnterType;
	}
	
	@Override
	public void onCreate(){
		logd("onCreate");
		super.onCreate();
		createAppDir();
		createMqttDir();
		createPhotoDir();
		createDevPhotoDir();
		createADDir();

		mPref = getSharedPreferences(SettingsConstants.GENERAL_SETTING, MODE_PRIVATE);
		mLastVisit = mPref.getString(SettingsConstants.KEY_LAST_VISIT, "none");
		
		userSignIn = mPref.getBoolean(SettingsConstants.KEY_SIGNIN_FLAG, userSignIn);
		mUser = mPref.getString(SettingsConstants.KEY_USERACCOUNT, null);
		
		if(userSignIn){
			mPassword = getPassword();
			mUID = mPref.getString(SettingsConstants.KEY_USERID, null);
			if((mPassword == null) || (mPassword.trim().length() < 6)){
				mPassword = null;
				mUID = null;
				userSignIn = false;
				Editor e = mPref.edit();
				e.putBoolean(SettingsConstants.KEY_SIGNIN_FLAG, userSignIn);
				e.putString(SettingsConstants.KEY_USERID, mUID);
				e.commit();
			}
		}
		//savedIdentifyCode = mPref.getString(SettingsConstants.KEY_IDENTIFY_CODE, null);
		mDataManager = new DataManager(this);
		
		registerActivityLifecycleCallbacks(new ActivityLifecycleCallbacks(){
			@Override
			public void onActivityCreated(Activity arg0, Bundle arg1) {}

			@Override
			public void onActivityDestroyed(Activity arg0) {}

			@Override
			public void onActivityPaused(Activity arg0) {}

			@Override
			public void onActivityResumed(Activity arg0) {
				mCurActivity = arg0;
			}

			@Override
			public void onActivitySaveInstanceState(Activity arg0, Bundle arg1){}

			@Override
			public void onActivityStarted(Activity arg0) {}

			@Override
			public void onActivityStopped(Activity arg0) {}
		});
		
		mADInfo = new HashMap<String, ADInfo>();
		initADInfo();
		SDKInitializer.initialize(this);		
	}
	
	/*class SessionTimeUp{
		int yy;
		int mm;
		int dd;
		int hh;
		int MM;
		int ss;
		
		SessionTimeUp(String timestring){
			String syy = timestring.substring(0,4);
			String smm = timestring.substring(4,6);
			String sdd = timestring.substring(6,8);
			String shh = timestring.substring(8,10);
			String sMM = timestring.substring(10,12);
			String sss = timestring.substring(12,14);
			
			yy = Integer.parseInt(syy);
			mm = Integer.parseInt(smm);
			dd = Integer.parseInt(sdd);
			hh = Integer.parseInt(shh);
			MM = Integer.parseInt(sMM);
			ss = Integer.parseInt(sss);
		}
		
		public boolean expired(){
			Time time = new Time();
			time.setToNow();
			int css = MM * 60 + ss;
			int tss = time.minute * 60 + time.second;
			
			if((time.year > yy) || (time.month > mm) || (time.monthDay > dd)
				|| (time.hour > hh) || ((tss - css) > -10)){
				return true;
			}
			return false;
		}
	}*/
	
	public boolean addADData(JSONArray arr) throws JSONException{
		int size = Math.min(arr.length(), AD_MAX_NUM);
		ADDebug("addADData, arr.length=" + arr.length());
		if(size <= 0)
			return false;
		
		removeAllADFiles();
		releaseAllAD();
		
		Editor edit = mPref.edit();
		for(int i=0; i<AD_MAX_NUM; i++){
			String key = SettingsConstants.KEY_AD_01;
			if(i == 1){
				key = SettingsConstants.KEY_AD_02;
			}else if(i == 2){
				key = SettingsConstants.KEY_AD_03;
			}
			ADInfo info = mADInfo.get(key);
			if(i < size){
				JSONObject e = arr.getJSONObject(i);
				ADDebug("JSONObject:" + e);
				edit.putString(key, e.toString());
				info.setADInfo(e.toString(), key);
			}else{
				edit.putString(key, "");
				info.setADInfo(null, key);
			}
		}
		edit.commit();
		
		loadADInfo(false);
		
		//Intent i = new Intent(ACTION_AD_UPDATE);
		//sendBroadcast(i);
		return true;
	}
	
	private void initADInfo(){
		if(mADInfo == null)
			return;
		
		ADDebug("initADInfo");
		
		try {
			String keyAD1 = SettingsConstants.KEY_AD_01;
			String adstr1 = mPref.getString(keyAD1, "");
			if(adstr1.trim().isEmpty()){
				adstr1 = null;
			}
			ADInfo adInfo1;
			adInfo1 = new ADInfo(adstr1, keyAD1, this);
			mADInfo.put(keyAD1, adInfo1);
			
			String keyAD2 = SettingsConstants.KEY_AD_02;
			String adstr2 = mPref.getString(keyAD2, "");
			if(adstr2.trim().isEmpty()){
				adstr2 = null;
			}
			ADInfo adInfo2 = new ADInfo(adstr2, keyAD2, this);
			mADInfo.put(keyAD2, adInfo2);
			
			String keyAD3 = SettingsConstants.KEY_AD_03;
			String adstr3 = mPref.getString(keyAD3, "");
			if(adstr3.trim().isEmpty()){
				adstr3 = null;
			}
			ADInfo adInfo3 = new ADInfo(adstr3, keyAD3, this);
			mADInfo.put(keyAD3, adInfo3);
		} catch (JSONException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	public void loadADInfo(boolean forceLocal){
		synchronized (mADInfo) {
			ADDebug("loadADInfo, forceLocal=" + forceLocal);
			
			Iterator<Entry<String, ADInfo>> iter = mADInfo.entrySet().iterator();
			while(iter.hasNext()){
				Entry<String,ADInfo> entry = (Entry<String,ADInfo>) iter.next();
				String key = entry.getKey();
				ADInfo info = entry.getValue();
				if(info.isClean() == false)
					info.loadBitmap(forceLocal);
			}			
		}
	}
	
	public int getADnumber(){

		synchronized (mADInfo) {
			int size = 0;
			/*
			for(Entry<String, ADInfo> ADsetting:mADInfo.entrySet()){
				ADInfo info = (ADInfo)ADsetting.getValue();
				if(info.isClean() == false)
					size ++;
			}*/
			Iterator<Entry<String, ADInfo>> iter = mADInfo.entrySet().iterator();
			while(iter.hasNext()){
				Entry<String,ADInfo> entry = (Entry<String,ADInfo>) iter.next();
				String key = entry.getKey();
				ADInfo info = entry.getValue();
				if(info.isClean() == false)
					size ++;
			}
			ADDebug("getADnumber:" + size);
			return size;
		}
	}
	
	public void showAD(ImageView iView, TextView tView, String key){
		ADInfo info = null;
		synchronized (mADInfo) {
			ADDebug("showAD, key=" + key);
			int arraysize = getADnumber();//mADArray.size();
			if(arraysize == 0){
				//tView.setText("为您定制");
				iView.setImageResource(R.drawable.ad_default);
				iView.setScaleType(ScaleType.FIT_XY);
				return;
			}
			if(mADInfo.containsKey(key)){
				info = mADInfo.get(key);
			}
		}
		if(info == null)
			return;
		
		if(info.isClean() == true){
			//info.showDescription(tView);
			iView.setImageResource(R.drawable.wait_icon);
			iView.setScaleType(ScaleType.CENTER_INSIDE);
		}else{
			if(info.show(iView) == false){
				info.showDescription(tView);
				iView.setImageResource(R.drawable.wait_icon);
				iView.setScaleType(ScaleType.CENTER_INSIDE);
				ADDebug("showAD, showImage false");
			}else{
				ADDebug("showAD, success!");
				info.showDescription(tView);
			}
		}
	}
	
	public void openADLink(String key){
		ADInfo info = null;
		synchronized (mADInfo) {
			info = mADInfo.get(key);
		}
		if(info == null)
			return;
		
		String uri = info.getUri();
		String visit = uri.toLowerCase();
		if(visit.startsWith("http") == false){
			visit = "http://"+visit;
		}
		ADDebug("openADLink, uri=" + visit);
		Uri weburi = Uri.parse(visit);
		Intent intent = new Intent(Intent.ACTION_VIEW, weburi);
		intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
		startActivity(intent);
	}
	
	public int getLocationQueryLatestMaxCount(){
		return 60;
	}
	
	public long getGlycoseQueryLatestMaxDays(){
		return 30;
	}	
	
	public long getBpQueryLatestMaxDays(){
		return 30;
	}
	
	public void setNewVersion(boolean set){
		newVersion = set;
	}
	
	public void checkNewVersion(){
		Log.d("UMENGUPDATE", "checkNewVersion");
		setNewVersion(false);
		
		UmengUpdateAgent.setDefault();
		UmengUpdateAgent.setUpdateAutoPopup(true);
		UmengUpdateAgent.setUpdateUIStyle(UpdateStatus.STYLE_NOTIFICATION);
		UmengUpdateAgent.setDeltaUpdate(false);
		UmengUpdateAgent.setRichNotification(true);
		UmengUpdateAgent.setUpdateListener(new UmengUpdateListener() {
			
			@Override
			public void onUpdateReturned(int status, UpdateResponse updateInfo) {
				// TODO Auto-generated method stub
				String version = "";
				if(updateInfo != null)
					version = updateInfo.version;
				switch(status){
				case UpdateStatus.Yes:
					Log.d("UMENGUPDATE", "onUpdateReturned:" + "Yes" + "; version=" + version);
					if(UmengUpdateAgent.isIgnore(getApplicationContext(), updateInfo) == false)
						setNewVersion(true);
					break;
				case UpdateStatus.No:
					Log.d("UMENGUPDATE", "onUpdateReturned:" + "No" + "; version=" + version);
					break;
				case UpdateStatus.NoneWifi:
					Log.d("UMENGUPDATE", "onUpdateReturned:" + "NoneWifi" + "; version=" + version);
					break;
				case UpdateStatus.Timeout:
					Log.d("UMENGUPDATE", "onUpdateReturned:" + "Timeout" + "; version=" + version);
					break;
				}
			}
		});
		UmengUpdateAgent.update(this);
	}
	
	public boolean hasNewVersion(){
		return newVersion;
	}
	
	public boolean isSignIn(){
		return checkLogInSession();
	}
	
	public String getUID(){
		return mUID;
	}
	
	private void setLogInSession(String session/*, String timestring*/){
		synchronized("SESSION_SYNC"){
			mSession = session;
			//mSTimeUp = new SessionTimeUp(timestring.trim());
		}
	}
	
	public void clearLogInSession(){
		synchronized("SESSION_SYNC"){
			//mSTimeUp = null;
			mSession = null;
		}
	}
	
	public boolean checkLogInSession(){
		synchronized("SESSION_SYNC"){
			/*if(mSTimeUp == null){
				return false;
			}else */if(mSession == null){
				return false;
			}/*else if(mSTimeUp.expired()){
				return false;
			}*/
			return true;
		}
	}
	
	public String getSession(){
		synchronized("SESSION_SYNC"){
			return mSession;
		}
	}
	
	public void signOut(){
		mPassword = null;
		mUID = null;
		userSignIn = false;
		clearLogInSession();
		Editor e = mPref.edit();
		e.putString(SettingsConstants.KEY_PASSWORD,null);
		e.putBoolean(SettingsConstants.KEY_SIGNIN_FLAG, false);
		e.putString(SettingsConstants.KEY_USERID, null);
		e.commit();
		
		mDataManager.stopBackGroundDataGrab();
		stopMQTT();
	}
	
	private void stopMQTT(){
		/*stop mqtt*/
		Intent si = new Intent(MqttService.STOP_MQTT_ACTION);
		startService(si);
	}
	
	private void startMQTT(){
		Intent si = new Intent(MqttService.START_MQTT_ACTION);
		startService(si);
	}
	
	private boolean updateSignInData(boolean in, JSONObject req, 
			String uid, String session, String timestring, String netState){
		if(in){//login
			if(req == null){
				Log.e(TAG,"updateSignInData fatal err");
				return false;
			}
			String pwd;
			try {
				mUser = req.getString("loginname");
				pwd = req.getString("password");
			} catch (JSONException e1) {
				// TODO Auto-generated catch block
				e1.printStackTrace();
				Log.e(TAG,"updateSignInData parse json fatal err");
				return false;
			}
			
			if((uid == null) || uid.trim().isEmpty()){
				Log.e(TAG,"updateSignInData parse uid fatal err");
				return false;
			}
			if((session == null) || session.trim().isEmpty()){
				Log.e(TAG,"updateSignInData parse session fatal err");
				return false;
			}
			/*if((timestring == null) || (timestring.trim().length() != 14)){
				Log.e(TAG,"updateSignInData parse sessionlosetime fatal err");
				return false;
			}*/
			setLogInSession(session.trim()/*,timestring.trim()*/);
			
			boolean uidChanged = false;
			if((mUID == null) || (mUID.equals(uid.trim()) == false)){
				uidChanged = true;
			}
			mUID = uid.trim();
			userSignIn = true;
			
			Editor e = mPref.edit();
			e.putBoolean(SettingsConstants.KEY_SIGNIN_FLAG, userSignIn);
			e.putString(SettingsConstants.KEY_USERACCOUNT, mUser);
			if(uidChanged){
				e.putString(SettingsConstants.KEY_USERID, mUID);
				mDataManager.setUserData(DataManager.F_USERDATA, null);
			}
			
			e.commit();
			
			savePassword(pwd);
			
			initMQTTSettings();
			startMQTT();
			
			Intent i = new Intent(ACTION_SIGN_IN_OUT);
			i.putExtra("state", true);
			i.putExtra("netstate", netState);
			sendBroadcast(i);
			logd("updateSignInData log in");
			return true;
		}else{
			//logout
			//mPassword = null;
			
			//userSignIn = false;
			//Editor e = mPref.edit();
			//e.putBoolean(SettingsConstants.KEY_SIGNIN_FLAG, userSignIn);
			//e.commit();
			//mUID = null;
			clearLogInSession();
			
			stopMQTT();
			
			Intent i = new Intent(ACTION_SIGN_IN_OUT);
			i.putExtra("state", false);
			i.putExtra("netstate", netState);
			sendBroadcast(i);
			logd("updateSignInData log out");
			return true;
		}
	}
	
	private void initMQTTSettings(){
		isMQTTMsgOn = mPref.getBoolean(SettingsConstants.KEY_MQTT_NOTICE_SWITCH, true);
		isMQTTSoundOn = mPref.getBoolean(SettingsConstants.KEY_MQTT_NOTICE_SOUND, true);
		isMQTTVibOn = mPref.getBoolean(SettingsConstants.KEY_MQTT_NOTICE_VIB, true);
		logd("initMQTTSettings");
	}
	
	public boolean getMQTTMsgOn(){
		return isMQTTMsgOn;
	}
	
	public boolean getMQTTSoundOn(){
		return isMQTTSoundOn;
	}
	
	public boolean getMQTTVibOn(){
		return isMQTTVibOn;
	}
	
	public void setMQTTMsgOn(boolean on){
		Editor e = mPref.edit();
		e.putBoolean(SettingsConstants.KEY_MQTT_NOTICE_SWITCH, on);
		e.commit();
		isMQTTMsgOn = on;
		logd("setMQTTMsgOn " + on);
	}
	
	public void setMQTTSoundOn(boolean on){
		Editor e = mPref.edit();
		e.putBoolean(SettingsConstants.KEY_MQTT_NOTICE_SOUND, on);
		e.commit();
		isMQTTSoundOn = on;
		logd("setMQTTSoundOn " + on);
	}
	
	public void setMQTTVibOn(boolean on){
		Editor e = mPref.edit();
		e.putBoolean(SettingsConstants.KEY_MQTT_NOTICE_VIB, on);
		e.commit();
		isMQTTVibOn = on;
		logd("setMQTTVibOn " + on);
	}
	
	private boolean createAppDir(){
		boolean externalUsed = false;
		String state = Environment.getExternalStorageState();
		if(state.equals(Environment.MEDIA_MOUNTED)){
			externalUsed = true;
		}
		
		if(externalUsed){
			appPath = Environment.getExternalStorageDirectory();
		}else{
			appPath = Environment.getDataDirectory();
		}	
		
		String root = getAppPath();
		if(root != null){
			File tmpFile=new File(root);
			if(tmpFile.exists() && tmpFile.isDirectory()){
				return true;
			}else{
				return tmpFile.mkdir();
			}
		}
		return false;
	}
	
	private void createADDir(){
		String path = getADPath();
		File tmpFile=new File(path);
		if(tmpFile.exists() && tmpFile.isDirectory()){
			//already exist
		}else{
			tmpFile.mkdirs();
		}
	}
	private void createMqttDir(){
		String path = getMqttPath();
		File tmpFile=new File(path);
		if(tmpFile.exists() && tmpFile.isDirectory()){
			//already exist
		}else{
			tmpFile.mkdirs();
		}
	}
	
	private void createPhotoDir(){
		String path = getPhotoPath();
		File tmpFile=new File(path);
		if(tmpFile.exists() && tmpFile.isDirectory()){
			//already exist
		}else{
			tmpFile.mkdirs();
		}
		
		String pathup = getUploadPhotoPath();
		File tmpFileUp=new File(pathup);
		if(tmpFileUp.exists() && tmpFileUp.isDirectory()){
			//already exist
		}else{
			tmpFileUp.mkdirs();
		}
		
		String pathDown = getDownloadPhotoPath();
		File tmpFileDown=new File(pathDown);
		if(tmpFileDown.exists() && tmpFileDown.isDirectory()){
			//already exist
		}else{
			tmpFileDown.mkdirs();
		}
	}
	
	public String getDownloadFaceFolder(){
		return getDownloadPhotoPath();
	}
	
	public String getUploadFaceFileName(){
		
		String path = getUploadPhotoPath();
		if((path == null) || path.isEmpty())
			return null;
		
		return path+"/upload.jpg";
	}
	
	public String getUploadFacePreCropFileName(){
		
		String path = getUploadPhotoPath();
		if((path == null) || path.isEmpty())
			return null;
		
		return path+"/precrop.jpg";
	}
	
	public String getQRTempJpgFileName(){
		String root = getAppPath();
		if((root == null) || root.isEmpty())
			return null;
		return root+"/qrcode.jpg";
	}
	
	public String getFaceFolder(){
		String path = getPhotoPath();
		return path;
	}
	
	public String getFaceFileName(String uid){
		if((uid == null) || uid.isEmpty())
			return null;
		
		String path = getPhotoPath();
		File folder = new File(path);
		File[] children = folder.listFiles();
		if((children != null) && (children.length > 0)){
			for(File f:children){
				if(f.isFile()){
					String fp = f.getPath();
					int pos = fp.lastIndexOf(File.separator);
					String name = fp.substring(pos+1);
					if(name.startsWith(uid)){
						return fp;
					}
				}
			}
		}
		return null;
	}
	
	private void createDevPhotoDir(){
		String path = getDevPhotoPath();
		File tmpFile=new File(path);
		if(tmpFile.exists() && tmpFile.isDirectory()){
			//already exist
		}else{
			tmpFile.mkdirs();
		}
	}
	
	public String getDevFaceFileName(String tid){
		if((tid == null) || tid.isEmpty())
			return null;
		
		String path = getDevPhotoPath();
		File folder = new File(path);
		File[] children = folder.listFiles();
		if((children != null) && (children.length > 0)){
			for(File f:children){
				if(f.isFile()){
					String fp = f.getPath();
					int pos = fp.lastIndexOf(File.separator);
					String name = fp.substring(pos+1);
					if(name.startsWith(tid)){
						return fp;
					}
				}
			}
		}
		return null;
	}
	
	private String getAppPath(){
		if(appPath != null){
			return appPath.getPath() + "/.dreamerfindu";
		}
		return null;
	}
	
	public String getADPath(){
		String root = getAppPath();
		
		if(root != null){
			return root + "/AD";
		}
		return null;
	}
	
	private String getPhotoPath(){
		String root = getAppPath();
		
		if(root != null){
			return root + "/photo";
		}
		return null;
	}
	
	public String getMqttPath(){
		String root = getAppPath();
		
		if(root != null){
			return root + "/mqtt";
		}
		return null;
	}
	
	private String getUploadPhotoPath(){
		String root = getPhotoPath();
		
		if(root != null){
			return root + "/up";
		}
		return null;

	}
	
	private String getDownloadPhotoPath(){
		String root = getPhotoPath();
		
		if(root != null){
			return root + "/down";
		}
		return null;

	}
	
	private String getDevPhotoPath(){
		String root = getAppPath();
		
		if(root != null){
			return root + "/devphoto";
		}
		return null;
	}
	
	public String getDevFaceFolder(){
		return getDevPhotoPath();
	}
	
	
	private Toast mNetErrToast = null;
	
	public boolean checkNetwork(){
		ConnectivityManager conManager = (ConnectivityManager)getSystemService(CONNECTIVITY_SERVICE);
		boolean netOk = false;
		
		if(conManager != null){
			NetworkInfo[] info = conManager.getAllNetworkInfo();
			if(info != null){
				for(int i=0; i<info.length; i++){
					if(info[i].getState() == NetworkInfo.State.CONNECTED){
						netOk = true;
						break;
					}
				}
			}
		}
		if(netOk == false){
			if(mNetErrToast == null){
				if(mCurActivity != null)
					mNetErrToast = Toast.makeText(mCurActivity, R.string.no_network_hint, Toast.LENGTH_LONG);	
			}
			if(mNetErrToast != null)
				mNetErrToast.show();
		}
		
		return netOk;
	}
	
	public void vibrate(){
		Vibrator vibrator = (Vibrator) getSystemService(VIBRATOR_SERVICE);
		vibrator.vibrate(300);
	}
	
	public String getLastVisit(){
		return "none";
		//return mLastVisit;
	}
	
	public void setlastVisit(String set){
		mLastVisit = set;
		Editor e = mPref.edit();
		e.putString(SettingsConstants.KEY_LAST_VISIT, mLastVisit);
		e.commit();
	}
	
	public boolean isUserSignIn(){
		return userSignIn;
	}
	
	public String getUserName(){
		mUser = mPref.getString(SettingsConstants.KEY_USERACCOUNT, null);
		return mUser;
	}
	
	public String getPassword(){
		String newBase64Pwd = mPref.getString(SettingsConstants.KEY_PASSWORD, null);
		
		if((null == newBase64Pwd) || newBase64Pwd.isEmpty()){
			return "";
		}
		byte[] b = Base64.decode(newBase64Pwd, 0);
		String mPassword = new String(b);
		
		return mPassword;
	}
	
	public void savePassword(String pwd){
		mPassword = pwd;
		Editor e = mPref.edit();
		String newBase64Pwd = Base64.encodeToString(mPassword.getBytes(), 0);
		
		e.putString(SettingsConstants.KEY_PASSWORD, newBase64Pwd);
		e.commit();
	}
	
	private void removeAllADFiles(){
		File filepath = new File(getADPath());
		ADDebug("removeAllADFiles, filepath:" + filepath);
		if(!filepath.exists() || !filepath.isDirectory()){
			ADDebug("removeAllADFiles failed!");
			return;
		}
		File[] children = filepath.listFiles();
		for(File f:children){
			if(f.exists() && f.isFile()){
				f.delete();
			}
		}
	}
	
	public void releaseAllAD(){
		synchronized (mADInfo) {

			Iterator<Entry<String, ADInfo>> iter = mADInfo.entrySet().iterator();
			while(iter.hasNext()){
				Entry<String,ADInfo> entry = (Entry<String,ADInfo>) iter.next();
				String key = entry.getKey();
				ADInfo info = entry.getValue();
				info.release();
				ADDebug("releaseAllAD, key=" + key);
			}
		}
	}
	
	public void releaseAllData(){
		if(mDataManager != null)
			mDataManager.releaseAll();
	}
	
	public boolean isMobileNumber(String num){
		if(num.length() == 11){
			char[] cs = num.toCharArray();
			for(char c:cs){
				if((c < '0') || (c >'9'))
					return false;
			}
			return true;
		}
		return false;
	}
	
	public String numberToHidenString(String num){
    	char[] cs = num.toCharArray();
		for(int i=(cs.length - 1); i>0; i--){
			if((i < (cs.length - 2)) && (i > (cs.length - 9))){
				cs[i]='*';
			}
		}
		String ret = new String(cs);
		return ret;
    }
	
	public boolean validUsername(String name){
		char f = name.charAt(0);
		return ((f >= 'A') && (f <= 'Z')) || ((f >= 'a') && (f <= 'z'));
	}
	
	private char[] UserNameChars = {'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z'
			,'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'
			,'0','1','2','3','4','5','6','7','8','9','0','!','@','-','_','+','.'};
	
	private char[] PasswordChars = {'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z'
			,'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'
			,'0','1','2','3','4','5','6','7','8','9','0','!','@','_'};
	
	public char[] getAllowedChars(String type){
		if("UserName".equalsIgnoreCase(type)){
			return UserNameChars;
		}
		
		if("Password".equalsIgnoreCase(type)){
			return PasswordChars;
		}
		
		
		return null;
	}
	
	public String validPassword(String password){
		char[] chars = password.toCharArray();
		for(char ch:chars){
			if((ch >= 0x30) && (ch <= 0x39)){
				continue;
			}
			
			if((ch >= 'A') && (ch <= 'Z')){
				continue;
			}
			
			if((ch >= 'a') && (ch <= 'z')){
				continue;
			}
			
			if((ch == '@') || (ch == '_') || (ch == '!')){
				continue;
			}
			
			String ret = String.valueOf(ch);
			return ret;
		}
		
		return null;
	}
	
	/*private void saveIdentifyCode(String code){		
		savedIdentifyCode = code;
		Editor e = mPref.edit();
		e.putString(SettingsConstants.KEY_IDENTIFY_CODE, savedIdentifyCode);
		e.commit();
	}*/
	
	/*public String getSavedIdentifyCode(){
		
		return savedIdentifyCode;
	}*/
	
	private HashMap<String,Handler> mNetHandler = new HashMap<String,Handler>();
	public static final int MSG_NET_RESPONSE = 903;
	public void addNetHandler(String stamp, Handler h){
		mNetHandler.put(stamp, h);
	}
	
	/*private boolean dealIdentifyCode(JSONObject data){
		try {
			int code = data.getInt("code");
			if(code == 200){
				String state = data.getString("state");
				if(state.equals("00")){
					JSONObject recdata = data.getJSONObject("recdata");
					if(recdata != null){
						String ic = recdata.getString("validcode");
						saveIdentifyCode(ic);
					}
				}
			}
		} catch (JSONException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		return false;
	}*/
	
	public boolean dealSignUp(JSONObject data){
		try {
			if(data != null){
				int code = data.getInt("code");
				if(code == 200){
					String state = data.getString("state");
					if(state.equals("01")){
						showAlertDialog(mCurActivity,R.string.signUpServerError);
						return false;
					}else if(state.equalsIgnoreCase("0B")){
						showAlertDialog(mCurActivity,R.string.signUpAccountExist);
						return false;
					}else if(state.equalsIgnoreCase("0C")){
						showAlertDialog(mCurActivity,R.string.signUpDataError);
						return false;
					}else if(state.equalsIgnoreCase("26")){
						showAlertDialog(mCurActivity,R.string.signUpMobileExist);
						return false;
					}else if(state.equals("00")){
						return false;
					}
				}
			}
		} catch (JSONException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		showAlertDialog(mCurActivity,R.string.signUpError);
		return false;
	}
	
	private boolean dealSignIn(JSONObject data, boolean auto){
		logd("dealSignIn auto = " + auto);
		try {
			if(data != null){
				int code = data.getInt("code");
				if(code == 200){
					String state = data.getString("state");
					if(state.equals("01")){
						updateSignInData(false,null,null,null,null,state);
						if(!auto)
							showAlertDialog(mCurActivity,R.string.signInServerError);
						return false;
					}else if(state.equals("02")){
						updateSignInData(false,null,null,null,null,state);
						if(!auto)
							showAlertDialog(mCurActivity,R.string.signInDataError);
						return false;
					}else if(state.equals("03")){
						//never be here
						updateSignInData(false,null,null,null,null,state);
						return false;
					}else if(state.equalsIgnoreCase("1B")){
						updateSignInData(false,null,null,null,null,state);
						if(!auto)
							showAlertDialog(mCurActivity,R.string.signInNoAccount);
						return false;
					}else if(state.equalsIgnoreCase("1C")){
						updateSignInData(false,null,null,null,null,state);
						if(!auto)
							showAlertDialog(mCurActivity,R.string.signInPwdError);
						return false;
					}else if(state.equals("00")){
						JSONObject sd = data.getJSONObject("senddata");
						JSONObject recdata = data.getJSONObject("recdata");
						if(recdata != null){
							String uid = recdata.getString("uid");
							String session = recdata.getString("sessioncode");
						//String stime = data.getString("sessionlosetime");
							
							if(false == updateSignInData(true,sd,uid, session, null ,state)){
								if(!auto)
									showAlertDialog(mCurActivity,R.string.signInDataError);
							}else{
								logd("log in ok");
								mDataManager.startBackGroundDataGrab();
							}
							return false;
						}else{
							updateSignInData(false,null,null,null,null,null);
							if(!auto)
								showAlertDialog(mCurActivity,R.string.signInDataError);
							return false;
						}
					}
				}
			}
		} catch (JSONException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		updateSignInData(false,null,null,null,null,null);
		if(!auto)
			showAlertDialog(mCurActivity,R.string.signInError);
		return false;
	}
	
	private boolean dealChangePassword(JSONObject data){
		logd("dealChangePassword");
		try {
			if(data != null){
				int code = data.getInt("code");
				if(code == 200){
					String state = data.getString("state");
					if(state.equals("00")){
						JSONObject sd = data.getJSONObject("senddata");
						String pwd = sd.getString("newpassword");
						savePassword(pwd);
					}
				}
			}
		} catch (JSONException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		return false;
	}
	
	public DataManager getDataManager(){
		return mDataManager;
	}
	
	public void dispatchNetResponse(String stamp, JSONObject data, boolean canceled){
		boolean consumed = false;
		/*if(stamp.startsWith("GET_IDENTIFY_CODE") && (data != null)){
			consumed = dealIdentifyCode(data);
		}else*/
		if(stamp.startsWith("SIGN_UP_NEW_ACCOUNT")){
			consumed = dealSignUp(data);
		}else if(stamp.startsWith("SIGN_IN_ACCOUNT")){
			boolean auto = stamp.startsWith("SIGN_IN_ACCOUNT_AUTO");
			consumed = dealSignIn(data,auto);
			setStatus(STATUS_LOGIN_PROCESSING, false);
		}else if(stamp.startsWith("CHANGE_PASSWORD")){
			consumed = dealChangePassword(data);
		}
		Handler h = mNetHandler.get(stamp);
		if(h != null){
			if(!consumed){
				Message m = h.obtainMessage(MSG_NET_RESPONSE);
				Bundle b = new Bundle();
				if(data != null)
					b.putString("json", data.toString());
				b.putString("stamp", stamp);
				b.putBoolean("canceled", canceled);
				m.setData(b);
				h.sendMessage(m);
			}
			mNetHandler.remove(stamp);
		}
	}
	
	private AlertDialog mWaitDialog = null;
	private ImageView animWaitIcon = null;
	
	public void showWaitting(Context context, OnCancelListener listener){
		if((mWaitDialog != null) && mWaitDialog.isShowing())
			return;
		
		LayoutInflater inflater = LayoutInflater.from(context);

		View dialogView = inflater.inflate(R.layout.wait_dialog, null);
		animWaitIcon = (ImageView)dialogView.findViewById(R.id.wait_star);
		Animation animWait = AnimationUtils.loadAnimation(context, R.anim.rotatecycled);
		
		mWaitDialog = new CustomDialog(context,R.style.CustomTransDialog, dialogView);
    	
		mWaitDialog.setCanceledOnTouchOutside(false);
		if(listener == null){
			mWaitDialog.setCancelable(false);
		}else{
			mWaitDialog.setCancelable(true);
			mWaitDialog.setOnCancelListener(listener);
		}
		
		mWaitDialog.setOnDismissListener(new OnDismissListener(){

			@Override
			public void onDismiss(DialogInterface arg0) {
				animWaitIcon.clearAnimation();
				mWaitDialog = null;
			}
			
		});
		
		mWaitDialog.show();
		animWaitIcon.startAnimation(animWait);
	}
	
	public void dismissWaiting(){
		if((mWaitDialog != null) && mWaitDialog.isShowing()){
			mWaitDialog.dismiss();
		}
	}
	
	public void showPickPhotoWin(Context context, final View.OnClickListener l){
		LayoutInflater inflater = LayoutInflater.from(context);

		View dialogView = inflater.inflate(R.layout.pick_photo_dialog, null);

		ImageView but1 = (ImageView)dialogView.findViewById(R.id.pick_cam);
		ImageView but2 = (ImageView)dialogView.findViewById(R.id.pick_album);
		ImageView but3 = (ImageView) dialogView.findViewById(R.id.cancel_but);
	    
	    final AlertDialog dialog = new CustomDialog(context,R.style.CustomDialog, dialogView);	
	    dialog.setCanceledOnTouchOutside(false);
	    
	    but1.setOnClickListener(new View.OnClickListener(){
			@Override
			public void onClick(View arg0) {
				dialog.dismiss();
				if(l!=null){
					l.onClick(arg0);
				}
			}
	    });
	    but2.setOnClickListener(new View.OnClickListener(){
			@Override
			public void onClick(View arg0) {
				dialog.dismiss();
				if(l!=null){
					l.onClick(arg0);
				}
			}
    	});
	    
	    but3.setOnClickListener(new View.OnClickListener(){
			@Override
			public void onClick(View arg0) {
				dialog.dismiss();
				if(l!=null){
					l.onClick(arg0);
				}
			}
    	});
	    	
	    dialog.show();
	}
	
	public void showAlertDialog(Context context, int res){
		showCustomizedDialog(context, null, getResources().getString(res), null, null, null);
	}

	public void showAlertDialog(Context context, String msg, final View.OnClickListener l){
		showCustomizedDialog(context, null, msg, null, null, l);
	}
	
	public void showAlertDialog(Context context, String msg, int butres, final View.OnClickListener l){
		showCustomizedDialog(context, null, msg, getResources().getString(butres), null, l);
	}
	
	public void showConfirmDialog(Context context, String msg, final View.OnClickListener l){		
		showCustomizedDialog(context, null,msg, getResources().getString(R.string.Yes),
				getResources().getString(R.string.No), l);
	}
	
	public void showCustomizedDialog(Context context, String title, String msg, String positive, String negative, final View.OnClickListener l){
		if(msg == null)
			return;
			
		LayoutInflater inflater = LayoutInflater.from(context);

		View dialogView = inflater.inflate(R.layout.custom_dialog, null);
		
		View top = dialogView.findViewById(R.id.top);
		TextView titleView = (TextView) dialogView.findViewById(R.id.alert_title);
		if(title != null){
			top.setVisibility(View.VISIBLE);
			titleView.setText(title);
		}else{
			top.setVisibility(View.GONE);
		}
	    TextView hint = (TextView)dialogView.findViewById(R.id.alert_hint);
	    	
	    hint.setText(msg);

	    LinearLayout but1 = (LinearLayout)dialogView.findViewById(R.id.alert_but1);
	    LinearLayout but2 = (LinearLayout)dialogView.findViewById(R.id.alert_but2);
	    ImageView but3 = (ImageView) dialogView.findViewById(R.id.cancel_but);
	    
	    if(positive != null){
	    	but3.setVisibility(View.GONE);
    		but1.setVisibility(View.VISIBLE);
    		TextView t1 = (TextView)but1.getChildAt(1);
	    	t1.setText(positive);
    	}
	    
	    if(negative != null){
	    	but3.setVisibility(View.GONE);
    		but2.setVisibility(View.VISIBLE);
    		TextView t2 = (TextView)but2.getChildAt(1);
	    	t2.setText(negative);
    	}else{
    		but2.setVisibility(View.GONE);
    	}
	    
	    if((positive == null) && (negative == null)){
	    	but3.setVisibility(View.VISIBLE);
	    	but1.setVisibility(View.GONE);
	    	but2.setVisibility(View.GONE);
	    }
    	
	    final AlertDialog dialog = new CustomDialog(context,R.style.CustomDialog, dialogView);	
	    dialog.setCanceledOnTouchOutside(false);
	    
	    but1.setOnClickListener(new View.OnClickListener(){
			@Override
			public void onClick(View arg0) {
				dialog.dismiss();
				if(l!=null){
					l.onClick(arg0);
				}
			}
	    });
	    but2.setOnClickListener(new View.OnClickListener(){
			@Override
			public void onClick(View arg0) {
				dialog.dismiss();
				if(l!=null){
					l.onClick(arg0);
				}
			}
    	});
	    
	    but3.setOnClickListener(new View.OnClickListener(){
			@Override
			public void onClick(View arg0) {
				dialog.dismiss();
				if(l!=null){
					l.onClick(arg0);
				}
			}
    	});
	    	
	    dialog.show();
	}
	
	public void showUmengNoUpgradeDialog(Context context){		
		LayoutInflater inflater = LayoutInflater.from(context);

		View dialogView = inflater.inflate(R.layout.umeng_noupdate_dialog, null);

	    Button ok = (Button) dialogView.findViewById(R.id.noupdate_ok);
    	
	    final AlertDialog dialog = new CustomDialog(context,R.style.CustomDialog, dialogView);	
	    dialog.setCanceledOnTouchOutside(false);
	    
	    ok.setOnClickListener(new View.OnClickListener(){
			@Override
			public void onClick(View arg0) {
				dialog.dismiss();
			}
	    });
	    dialog.show();
	}
	
	public static int STATUS_IDLE = 0x00;
	public static int STATUS_LOGIN_PROCESSING = 0x01;
	
	private int mStatus = STATUS_IDLE;
	
	public void setStatus(int status, boolean set){
		synchronized("STATUS_SYNC"){
			if(set){
				mStatus |= status;
			}else{
				mStatus &= ~status;
			}
		}
	}
	
	public boolean getStatus(int status){
		synchronized("STATUS_SYNC"){
			return ((mStatus&status) == status);
		}
	}
	
	//ADose choose list
	public void updateDoseChooseList(ADose dose){
		
	}
	
	public void initDoseChooseList(){
		if(doseChooseList.size() != 0){
			return;
		}
		
		try {
			InputStreamReader inputReader = new InputStreamReader(getResources().getAssets().open(DRUG_LIST_FILE));
			BufferedReader bufReader = new BufferedReader(inputReader);
			String line = "";
			while((line = bufReader.readLine()) != null){
				logd("line: " + line);
				JSONObject json = new JSONObject(line);
				ADose d = new ADose();
				d.drugname = json.getString("name");
				d.drugtype = json.getString("type");
				d.drugunit = json.getString("unit");
				doseChooseList.add(d);
			}
			
		} catch (Exception e) {
			// TODO: handle exception
			e.printStackTrace();
		} 
	}
	
	public List<ADose> getADoseFromChooseList(){
		return doseChooseList;
	}

}
